package lembrete.core.beans;

import java.io.FileNotFoundException;
import java.util.List;

import lembrete.core.dao.Factory;
import lembrete.core.dao.GrupoDao;
import lembrete.core.exceptions.ExcecaoBD;
import lembrete.core.exceptions.ExcecaoParametroInvalido;
import lembrete.core.exceptions.LembreteException;
/**
 * Essa classe representa um gerenciador de grupos, o qual
 * eh responsavel pelas operacoes relacionadas aos grupos.
 * 
 * @author Everton Leandro <br>
 *         Odilon Francisco <br>
 *         Daniel Coelho <br>
 * @version 1.0 
 */
public class GerenciadorDeGrupos {
	
	private static GerenciadorDeGrupos gerenciador = null;
	private GrupoDao grupoDao;
	private Long gruposId;
	
	/**
	 * Metodo que retorna uma instancia da classe GerenciadorDeGrupos, seguindo o
	 * padrao Factory.
	 * 
	 * @return instancia da classe
	 */
	public static GerenciadorDeGrupos getInstance() {
		if (gerenciador == null) {
            gerenciador = new GerenciadorDeGrupos();
        }
        return gerenciador;
	}
	
	/**
	 * Metodo criador.
	 */
	private GerenciadorDeGrupos(){
		grupoDao = Factory.createGrupoDao();
		gruposId = 0l;
    }

	/**
	 * Obtem id dos grupos
	 * 
	 * @return id dos grupos
	 */
	public Long getGruposId() {
		return gruposId;
	}

	/**
	 * Atualiza o id dos grupos
	 * 
	 * @param gruposId
	 */
	public void setGruposId(Long gruposId) {
		this.gruposId = gruposId;
	}
	
	/**
	 * Cria um novo grupo, com nome, gerente e opcao de ser editavel.
	 * 
	 * @param nome
	 * @param gerenteEmail
	 * @param editavel
	 * @return
	 * @throws ExcecaoParametroInvalido
	 * @throws ExcecaoBD
	 * @throws FileNotFoundException
	 */
	public Long criarGrupo(String nome, String gerenteEmail, String editavel) throws ExcecaoParametroInvalido, ExcecaoBD, FileNotFoundException {
		Long grupoId = getGruposId()+1; 
		setGruposId(grupoId);
		boolean b = new Boolean(editavel); 
		return grupoDao.criarGrupo(nome, gerenteEmail, b, grupoId);
		
	}

	/**
	 * Adiciona uma entrada a um grupo.
	 * 
	 * @param idUsuario
	 * @param idGrupo
	 * @param entrada
	 * @throws ExcecaoParametroInvalido
	 * @throws FileNotFoundException
	 * @throws ExcecaoBD
	 */
	public void adicionarEntrada(String idUsuario, String idGrupo,
			Entrada entrada) throws ExcecaoParametroInvalido, FileNotFoundException, ExcecaoBD {
		grupoDao.adicionarEntradaGrupo(idGrupo, idUsuario, entrada);
	}

	/**
	 * Cadastra um usuario como gerente do grupo.
	 * 
	 * @param idGrupo
	 * @param emailusuario
	 * @throws FileNotFoundException
	 * @throws ExcecaoParametroInvalido
	 * @throws ExcecaoBD
	 */
	public void cadastraGerenteGrupo(Long idGrupo, String emailusuario) throws FileNotFoundException, ExcecaoParametroInvalido, ExcecaoBD {
		grupoDao.cadastraGerenteGrupo(idGrupo, emailusuario);
	}
	
	/**
	 * Retorna um grupo como String.
	 * 
	 * @param idUsuario
	 * @param idGrupo
	 * @return grupo pedido
	 * @throws ExcecaoParametroInvalido
	 */
	public String visualizarGrupo(String idUsuario, String idGrupo) throws ExcecaoParametroInvalido {
		try {
			return grupoDao.localizaGrupo(idUsuario, idGrupo).toString();
		} catch (Exception e) {
			throw new ExcecaoParametroInvalido("Usuario nao cadastrado no grupo.");
		}
	}

	/**
	 * Remove todos os grupos armazenados no banco de dados.
	 * 
	 * @throws FileNotFoundException
	 * @throws ExcecaoBD
	 */
	public void removeTodosGrupos() throws FileNotFoundException, ExcecaoBD {
		grupoDao.limpaBD();
		Factory.createGrupoDao().limpaBD();
	}

	/**
	 * Inicia o banco de dados onde serao armazenados os dados
	 * do sistema.
	 * 
	 * @param nomeBD
	 * @throws ExcecaoBD
	 * @throws FileNotFoundException
	 */
	public void usarBancoDeDados(String nomeBD) throws ExcecaoBD, FileNotFoundException {
		grupoDao.setBD(nomeBD);		
	}

	/**
	 * Edita uma entrada em um grupo.
	 * 
	 * @param idUsuario
	 * @param idGrupo
	 * @param idEntrada
	 * @param nomeCampoAntigo
	 * @param novoValor
	 * @throws FileNotFoundException
	 * @throws ExcecaoParametroInvalido
	 * @throws ExcecaoBD
	 */
	public void editarEntrada(String idUsuario, String idGrupo,
			Entrada entrada, String campo, String novoValor) throws FileNotFoundException, ExcecaoParametroInvalido, ExcecaoBD {
		grupoDao.editarEntrada(idUsuario, idGrupo, entrada, campo, novoValor);
		
	}

	/**
	 * Salva modificacoes feitas no grupo.
	 * 
	 * @throws FileNotFoundException
	 * @throws ExcecaoBD
	 */
	public void salvaModificacoes() throws FileNotFoundException, ExcecaoBD {
		grupoDao.salvaModificacoes();
	}

	/**
	 * Exclui uma entrada do grupo.
	 * 
	 * @param emailUsuario
	 * @param idGrupo
	 * @param entrada
	 * @throws ExcecaoParametroInvalido
	 * @throws FileNotFoundException
	 * @throws ExcecaoBD
	 */
	public void excluirEntrada(String emailUsuario, String idGrupo,
			Entrada entrada) throws ExcecaoParametroInvalido, FileNotFoundException, ExcecaoBD {
		grupoDao.excluiEntrada(emailUsuario, idGrupo, entrada);
		
	}
	
	/**
	 * Compartilha um grupo com outros usuarios.
	 * 
	 * @param idGerente
	 * @param idGrupo
	 * @param listaUsuarios
	 * @throws ExcecaoParametroInvalido
	 * @throws ExcecaoBD 
	 * @throws FileNotFoundException 
	 */
	public void compartilharGrupo(String idGerente, String idGrupo,	List<String> listaUsuarios) throws ExcecaoParametroInvalido, FileNotFoundException, ExcecaoBD {
		grupoDao.compartilharGrupo(idGerente,idGrupo,listaUsuarios);
	}
	
	/**
	 * Muda permissao de grupo, para torna-lo editavel ou nao.
	 * 
	 * @param idGrupo
	 * @param idGerente
	 * @param editavel
	 * @throws ExcecaoParametroInvalido
	 * @throws LembreteException
	 */
	public void mudarPermissaoGrupo(String idGrupo, String idGerente, String editavel) throws ExcecaoParametroInvalido, LembreteException{
		grupoDao.mudarPermissaoGrupo(idGrupo, idGerente, editavel);
	}
	
	/**
	 * Confirma que o usuario participara do compartilhamento do grupo.
	 * 
	 * @param idUsuario
	 * @param idGrupo
	 * @throws ExcecaoParametroInvalido
	 * @throws ExcecaoBD 
	 * @throws FileNotFoundException 
	 */
	public void confirmarParticipacaoCompartilhamento(String idUsuario, String idGrupo) throws ExcecaoParametroInvalido, ExcecaoBD, FileNotFoundException{
		grupoDao.confirmarParticipacaoCompartilhamento(idUsuario, idGrupo);
	}

	/**
	 * Verifica se um usuario participa do grupo
	 * 
	 * @param idGrupo
	 * @param idUsuario
	 * @return true se o usuario participa do grupo, false caso contrario
	 */
	public boolean usuarioParticipaGrupo(String idGrupo, String idUsuario) {
		return grupoDao.usuarioParticipaGrupo(idGrupo, idUsuario);
	}

	/**
	 * Verifica se um usuario tem permissao para editar um grupo
	 * 
	 * @param idGrupo
	 * @param idUsuario
	 * @return true se o usuario possui permissao, false caso contrario
	 */
	public boolean usuarioTemPermissaoDeEdicao(String idGrupo, String idUsuario) throws ExcecaoParametroInvalido {
		if (!grupoDao.usuarioTemPermissaoDeEdicao(idGrupo, idUsuario))
			throw new ExcecaoParametroInvalido("Permissao negada.");
		return true;
	}

	public Grupo getGrupoPorId(Long id) {
		return grupoDao.localizaGrupo(id);		
	}

	public static GerenciadorDeGrupos getGerenciador() {
		return gerenciador;
	}

	public static void setGerenciador(GerenciadorDeGrupos gerenciador) {
		GerenciadorDeGrupos.gerenciador = gerenciador;
	}

	public GrupoDao getGrupoDao() {
		return grupoDao;
	}

	public void setGrupoDao(GrupoDao grupoDao) {
		this.grupoDao = grupoDao;
	}

	public void excluirEntrada(Entrada entrada) throws FileNotFoundException, ExcecaoBD{
		grupoDao.excluirEntrada(entrada);		
	}

	public void editarEntrada(Entrada entrada,String campo, String novoValor) throws FileNotFoundException, ExcecaoBD {
		grupoDao.editarEntrada(entrada, campo, novoValor);
		
	}
	
	public void sendMail() throws LembreteException{
		grupoDao.sendMail();
	}

}


